﻿using System.Windows.Input;
using DDU.DataModel;
using DDU.Library;
using Microsoft.Phone.Tasks;
using System.IO.IsolatedStorage;
using System;
using System.IO;
using System.Windows;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;

namespace DDU.ViewModel
{
    public class BookAddViewModel : MainViewModel
    {
        PhotoChooserTask photoChooser = new PhotoChooserTask() { ShowCamera = true };
        CameraCaptureTask cameraCapture = new CameraCaptureTask();

        public BookAddViewModel()
        {
            BookToAdd.ValueChanged -= BookToAdd_ValueChanged;
            BookToAdd.ValueChanged += BookToAdd_ValueChanged;

            photoChooser.Completed -= PhotoChooser_Completed;
            photoChooser.Completed += PhotoChooser_Completed;

            cameraCapture.Completed -= cameraCapture_Completed;
            cameraCapture.Completed += cameraCapture_Completed;
        }

        void BookToAdd_ValueChanged(object sender, PropertyArgs e)
        {
            RaisePropertyChanged(() => AddCommand);
        }

        #region Properties
        private SemesterInfo selectedSemester;
        public SemesterInfo SelectedSemester
        {
            get { return selectedSemester; }
            set
            {
                selectedSemester = value;
                RaisePropertyChanged(() => SelectedSemester);
                RaisePropertyChanged(() => CanAdd);
                BookToAdd.SemesterGuid = SelectedSemester.Guid;
                RaisePropertyChanged(() => BookToAdd);
            }
        }

        public bool CanAdd
        {
            get
            {
                //return true;
                return IsDesignMode ? true : SelectedSemester != null;
            }
        }

        private BookInfo bookToAdd = new BookInfo();
        public BookInfo BookToAdd
        {
            get { return bookToAdd; }
            set
            {
                bookToAdd = value;
                RaisePropertyChanged(() => BookToAdd);

                BookToAdd.ValueChanged -= BookToAdd_ValueChanged;
                BookToAdd.ValueChanged += BookToAdd_ValueChanged;
            }
        }

        private Visibility contentPanelVisibility = Visibility.Visible;
        public Visibility ContentPanelVisibility
        {
            get { return contentPanelVisibility; }
            set
            {
                contentPanelVisibility = value;
                RaisePropertyChanged(() => ContentPanelVisibility);
            }
        }

        private Visibility galleryPanelVisibility = Visibility.Collapsed;
        public Visibility GalleryPanelVisibility
        {
            get { return galleryPanelVisibility; }
            set
            {
                galleryPanelVisibility = value;
                RaisePropertyChanged(() => GalleryPanelVisibility);
            }
        }

        public ObservableCollection<StoredBookCoverInfo> StoredCoverImages
        {
            get
            {
                if (IsDesignMode)
                {
                    return null;
                }
                using (IsolatedStorageFile store = IsolatedStorageFile.GetUserStoreForApplication())
                {
                    return new ObservableCollection<StoredBookCoverInfo>(store.GetFileNames(ConstKeys.BookDirectoryName + "\\*.*").Select(s => new StoredBookCoverInfo(ConstKeys.BookDirectoryName + "\\" + s)));
                }
            }
        }

        private StoredBookCoverInfo selectedCover;
        public StoredBookCoverInfo SelectedCover
        {
            get { return selectedCover; }
            set
            {
                selectedCover = value;
                RaisePropertyChanged(() => SelectedCover);
                RaisePropertyChanged(() => SelectedOKCommand);
            }
        }
        #endregion

        #region Commands
        public ICommand BarcodeCommand
        {
            get
            {
                return new GenericCommand()
                {
                    CanExecuteCallback = delegate { return false; }
                };
            }
        }

        public ICommand ChooseCommand
        {
            get
            {
                return new GenericCommand()
                {
                    ExecuteCallback = delegate { photoChooser.Show(); }
                };
            }
        }

        public ICommand CameraCommand
        {
            get
            {
                return new GenericCommand()
                {
                    ExecuteCallback = delegate { cameraCapture.Show(); }
                };
            }
        }

        public ICommand AddCommand
        {
            get
            {
                return new GenericCommand()
                {
                    CanExecuteCallback = delegate { return !string.IsNullOrWhiteSpace(BookToAdd.Title) && !string.IsNullOrWhiteSpace(BookToAdd.Image) && CanAdd; },
                    ExecuteCallback = delegate { Insert(BookToAdd); }
                };
            }
        }

        public ICommand CancelCommand
        {
            get
            {
                return new GenericCommand()
                {
                    ExecuteCallback = delegate
                    {
                        if (BackUri != null)
                        {
                            Navigate(BackUri);
                        }
                    }
                };
            }
        }

        public ICommand OpenGalleryCommand
        {
            get
            {
                return new GenericCommand()
                {
                    ExecuteCallback = delegate
                    {
                        ContentPanelVisibility = Visibility.Collapsed;
                        GalleryPanelVisibility = Visibility.Visible;
                    }
                };
            }
        }

        public ICommand SelectedOKCommand
        {
            get
            {
                return new GenericCommand()
                {
                    CanExecuteCallback = delegate { return SelectedCover != null; },
                    ExecuteCallback = delegate {
                        BookToAdd.Image = SelectedCover.FileName;
                        HideGalleryCommand.Execute(null);
                    }
                };
            }
        }

        public ICommand HideGalleryCommand
        {
            get
            {
                return new GenericCommand()
                {
                    //CanExecuteCallback = delegate { return SelectedCover != null; },
                    ExecuteCallback = delegate
                    {
                        ContentPanelVisibility = Visibility.Visible;
                        GalleryPanelVisibility = Visibility.Collapsed;
                        SelectedCover = null;
                        RaisePropertyChanged(() => SelectedCover);
                        RaisePropertyChanged(() => SelectedOKCommand);
                    }
                };
            }
        }
        #endregion

        #region Method

        void Insert(BookInfo entity)
        {
            Database.CollectionOfBooks.InsertOnSubmit(entity);
            Submit();
            BookToAdd = new BookInfo();
            RaisePropertyChanged(() => BookToAdd);
            RaisePropertyChanged(() => AddCommand);
        }

        void cameraCapture_Completed(object sender, PhotoResult e)
        {
            SavePhoto(e);
        }

        void PhotoChooser_Completed(object sender, PhotoResult e)
        {
            SavePhoto(e);
        }

        void SavePhoto(PhotoResult e)
        {
            if (e.TaskResult == TaskResult.OK)
            {
                using (BinaryReader reader = new BinaryReader(e.ChosenPhoto))
                {
                    using (IsolatedStorageFile store = IsolatedStorageFile.GetUserStoreForApplication())
                    {
                        string fileName = ConstKeys.BookDirectoryName + "\\" + DateTime.Now.Ticks + Path.GetExtension(e.OriginalFileName);

                        if (store.FileExists(fileName))
                        {
                            store.DeleteFile(fileName);
                        }

                        using (IsolatedStorageFileStream fileStream = store.OpenFile(fileName, FileMode.OpenOrCreate, FileAccess.Write))
                        {
                            using (BinaryWriter writer = new BinaryWriter(fileStream))
                            {
                                writer.Write(reader.ReadBytes(Convert.ToInt32(e.ChosenPhoto.Length)));
                            }

                            fileStream.Close();
                            fileStream.Dispose();
                        }

                        BookToAdd.Image = fileName;
                        RaisePropertyChanged(() => BookToAdd);
                    }
                }
            }
        }
        #endregion
    }
}
